package controllers

import (
	"fmt"
	"ginstudydemo.com/main/models"
	"ginstudydemo.com/main/service"
	"github.com/gin-gonic/gin"
	"strconv"
)

type IRoleController interface {
	GetRolesPage()
}

type RoleController struct{}

func NewRoleController() *RoleController {
	return &RoleController{}
}

// GetRolesPage 角色分页列表
func (u RoleController) GetRolesPage(c *gin.Context) {

	var query models.SysRolePageListParams
	var pagination models.PaginationParams
	// 获取查询参数（除分页参数）
	if err := c.ShouldBindQuery(&query); err != nil {
		service.ReturnErr(c, "9999", err.Error())
		c.Abort() // 终止后续处理
		return    // 确保不会继续执行后续代码
	}

	// 获取分页参数
	if err := c.ShouldBindQuery(&pagination); err != nil {
		service.ReturnErr(c, "9999", err.Error())
		c.Abort() // 终止后续处理
		return    // 确保不会继续执行后续代码
	}

	data, count, pageNum, pageSize, modelErr := models.GetRolePageList(query, pagination)

	if !(modelErr == nil) {
		service.ReturnErr(c, "9999", modelErr.Error())
		c.Abort()
		return
	}

	service.ReturnSuccess[models.SysRolePageListRes](c, "2000", "ok", models.SysRolePageListRes{
		Total:    count,
		PageSize: pageSize,
		PageNum:  pageNum,
		List:     data,
	})
}

// GetRolesOptions 角色下拉列表
func (u RoleController) GetRolesOptions(c *gin.Context) {

	data, modelErr := models.GetRolesOptions()
	if !(modelErr == nil) {
		service.ReturnErr(c, "9999", modelErr.Error())
		c.Abort()
		return
	}
	service.ReturnSuccess[[]models.SysRoleOptions](c, "2000", "ok", data)
}

// AddRole 新增后台系统用户
func (u RoleController) AddRole(c *gin.Context) {
	//使用数据表结构体获取参数
	param := &models.RoleForm{}
	// 把结构体指针传入BindJSON，这样param的值才能同步修改
	cErr := c.BindJSON(param)
	if !(cErr == nil) {
		service.ReturnErr(c, "9999", cErr.Error())
		c.Abort()
		return
	}
	//TODO：表单数据验证

	fmt.Println("=======")
	fmt.Println(*param)
	fmt.Println("=======")
	userId, modelErr := models.AddRole(*param)
	if !(modelErr == nil) {
		service.ReturnErr(c, "9999", modelErr.Error())
		c.Abort()
		return
	}

	service.ReturnSuccess[int64](c, "2000", "ok", userId)

}

// GetRoleFormById 根据id获取用户表单数据
func (u RoleController) GetRoleFormById(c *gin.Context) {
	roleId := c.Param("roleId")

	data, modelErr := models.GetRoleFromById(roleId)
	if !(modelErr == nil) {
		service.ReturnErr(c, "9999", modelErr.Error())
		c.Abort()
		return
	}

	service.ReturnSuccess(c, "2000", "ok", data)
}

// EditRole 修改后台系统用户
func (u RoleController) EditRole(c *gin.Context) {

	roleId := c.Param("roleId")

	//使用数据表空结构体获取参数
	param := &models.SysRoleFormData{}
	// 把结构体指针传入BindJSON，这样param的值才能同步修改
	cErr := c.BindJSON(param)
	if !(cErr == nil) {
		service.ReturnErr(c, "9999", cErr.Error())
		c.Abort()
		return
	}

	//TODO：表单数据验证 EditRole
	fmt.Println("=======")
	fmt.Println(*param)
	fmt.Println("=======")
	modelErr := models.EditRole(*param, roleId)
	if !(modelErr == nil) {
		service.ReturnErr(c, "9999", modelErr.Error())
		c.Abort()
		return
	}
	service.ReturnSuccess(c, "2000", "ok", struct{}{})

}

// DelRoles 批量删除
func (u RoleController) DelRoles(c *gin.Context) {

	roleIds := c.Param("ids")

	if roleIds == "" {
		service.ReturnErr(c, "9999", "error:ids为空")
		c.Abort() // 终止后续处理
		return    // 确保不会继续执行后续代码
	}

	modelErr := models.DelRoleSoftByIds(roleIds)
	if !(modelErr == nil) {
		service.ReturnErr(c, "9999", modelErr.Error())
		c.Abort() // 终止后续处理
		return    // 确保不会继续执行后续代码
	}
	service.ReturnSuccess(c, "2000", "ok", struct{}{})
}

// GetMenuIdsByRoleId 获取角色的菜单ID集合
func (u RoleController) GetMenuIdsByRoleId(c *gin.Context) {

	roleId := c.Param("roleId")

	if roleId == "" {
		service.ReturnErr(c, "9999", "error:ids为空")
		c.Abort() // 终止后续处理
		return    // 确保不会继续执行后续代码
	}

	fmt.Println("=======")
	fmt.Println(roleId)
	fmt.Println("=======")

	ids, modelErr := models.GetMenuIdsByRoleId(roleId)
	if !(modelErr == nil) {
		service.ReturnErr(c, "9999", modelErr.Error())
		c.Abort() // 终止后续处理
		return    // 确保不会继续执行后续代码
	}

	service.ReturnSuccess(c, "2000", "ok", ids)

}

// AddRolesMenus 分配菜单(包括按钮权限)给角色 roles/{roleId}/menus
func (u RoleController) AddRolesMenus(c *gin.Context) {
	roleId := c.Param("roleId")

	if roleId == "" {
		service.ReturnErr(c, "9999", "error:ids为空")
		c.Abort() // 终止后续处理
		return    // 确保不会继续执行后续代码
	}

	//使用数据表空结构体获取参数
	var param []int64
	// 把结构体指针传入BindJSON，这样param的值才能同步修改
	cErr := c.BindJSON(&param)
	if !(cErr == nil) {
		service.ReturnErr(c, "5000", cErr)
		c.Abort()
		return
	}

	fmt.Println("=======")
	fmt.Println(roleId)
	fmt.Println("=======")

	fmt.Println("=======")
	fmt.Println(param)
	fmt.Println("=======")

	// 获取角色信息,判断角色是否存在
	roleInfo, mErr3 := models.GetRoleFromById(roleId)
	if !(mErr3 == nil) {
		service.ReturnErr(c, "9999", mErr3.Error())
		c.Abort() // 终止后续处理
		return    // 确保不会继续执行后续代码
	}
	if roleInfo.ID == 0 {
		service.ReturnErr(c, "9999", "error:角色不存在")
		c.Abort() // 终止后续处理
		return    // 确保不会继续执行后续代码
	}

	// 清空角色对应的
	mErr2 := models.DelRoleMenuByRoleId(roleId)
	if !(mErr2 == nil) {
		service.ReturnErr(c, "9999", "error:清空角色菜单失败")
		c.Abort() // 终止后续处理
		return    // 确保不会继续执行后续代码
	}

	// 重新添加角色对应的菜单
	roleIdInt, _ := strconv.ParseInt(roleId, 10, 64)
	modelErr := models.AddRoleMenus(roleIdInt, param)
	if !(modelErr == nil) {
		service.ReturnErr(c, "9999", modelErr.Error())
		c.Abort() // 终止后续处理
		return    // 确保不会继续执行后续代码
	}

	// 获取角色按钮权限列表
	modelPerms, modelPermsErr := models.GetSysRoleMenuPerm(roleInfo.Code)
	if !(modelPermsErr == nil) {
		service.ReturnErr(c, "9999", modelPermsErr.Error())
		c.Abort()
		return
	}
	// 将角色按钮权限列表存入Redis哈希表
	service.NewAuthService().SavePermsAsGoHashSetToRedis(roleInfo.Code, *modelPerms)

	service.ReturnSuccess(c, "2000", "ok", struct{}{})

}

// EditRoleStatus 修改角色状态
func (u RoleController) EditRoleStatus(c *gin.Context) {
	roleId := c.Param("roleId")
	var query models.SysStatus
	if err := c.ShouldBindQuery(&query); err != nil {
		service.ReturnErr(c, "9999", err.Error())
		c.Abort() // 终止后续处理
		return    // 确保不会继续执行后续代码
	}

	modelErr := models.EditRoleStatus(query, roleId)
	if !(modelErr == nil) {
		service.ReturnErr(c, "9999", modelErr.Error())
		c.Abort() // 终止后续处理
		return    // 确保不会继续执行后续代码
	}
	service.ReturnSuccess(c, "2000", "ok", struct{}{})
}
